package com.example.school.service.impl;

import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.metadata.IPage;
import com.baomidou.mybatisplus.core.toolkit.CollectionUtils;
import com.baomidou.mybatisplus.core.toolkit.Wrappers;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.example.school.dto.*;
import com.example.school.mapper.SemesterMapper;
import com.example.school.mapper.UserMapper;
import com.example.school.pojo.Course;
import com.example.school.pojo.Semester;
import com.example.school.pojo.User;
import com.example.school.service.CourseService;
import com.example.school.mapper.CourseMapper;
import com.example.school.service.SemesterService;
import com.example.school.utils.common.enums.Code;
import com.example.school.utils.common.result.PageResponseResult;
import com.example.school.utils.common.result.Result;
import com.example.school.utils.config.BaseContext;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.scheduling.annotation.Async;
import org.springframework.stereotype.Service;

import java.util.HashMap;
import java.util.List;
import java.util.Map;

/**
* @author 24354
* @description 针对表【course】的数据库操作Service实现
* @createDate 2024-03-16 23:27:01
*/
@Service
@Slf4j
public class CourseServiceImpl extends ServiceImpl<CourseMapper, Course>
    implements CourseService{

    @Autowired
    private CourseMapper courseMapper;
    @Autowired
    private UserMapper userMapper;
    @Autowired
    private SemesterService semesterService;
    @Autowired
    private SemesterMapper semesterMapper;

    @Override
    public Result getUserCourseList(Integer week,Long semesterId) {

        Integer checkWeek=1;
        if (week!=null) {
            checkWeek=week;
        }
        String checkSemester = checkSemester(semesterId);
        log.info("checkSemester:{}",checkSemester);

        Long userId = BaseContext.getCurrentId();
        User checkUser = userMapper.selectById(userId);
        if (userId==null||checkUser==null) {
            return Result.errorResult(Code.NEED_LOGIN);
        }
        List<Course> courseList = courseMapper.selectList(Wrappers.<Course>lambdaQuery()
                .le(Course::getCourseWeekStart, checkWeek)
                .ge(Course::getCourseWeekEnd,checkWeek)
                .eq(Course::getSemesterId,checkSemester)
                .eq(Course::getGrade,checkUser.getStudentGrade()));
        return Result.okResult(courseList);
    }

    @Override
    public Result saveCourse(AdminCourseSaveDto dto) {

        if (dto==null) {
            return Result.errorResult(Code.PARAM_REQUIRE);
        }
        if (BaseContext.getCurrentId()==null) {
            return Result.errorResult(Code.NEED_LOGIN);
        }
        List<Course> checkCourseList = courseMapper.selectList(Wrappers.<Course>lambdaQuery()
                .eq(Course::getCourseName, dto.getName()));
        if (!CollectionUtils.isEmpty(checkCourseList)&&checkCourseList.size()>0) {
            return Result.errorResult(Code.DATA_EXIST);
        }
        Course course=new Course();
        course.setCourseName(dto.getName());
        course.setCourseDay(dto.getDay());
        course.setCourseWeekStart(dto.getWeekStart());
        course.setCourseWeekEnd(dto.getWeekEnd());
        course.setCourseTimeStart(dto.getTimeStart());
        course.setCourseTimeEnd(dto.getTimeEnd());
        course.setCourseAddress(dto.getAddress());
        course.setCourseTeacher(dto.getTeacher());
        course.setSemesterId(dto.getSemesterId());
        course.setGrade(dto.getGrade());
        int checkSave = courseMapper.insert(course);
        if (checkSave==0) {
            return Result.errorResult(Code.SERVER_ERROR);
        }
        return Result.okResult(Code.SUCCESS);
    }

    @Override
    public Result removeCourse(AdminCourseRemoveDto dto) {

        if (dto==null) {
            return Result.errorResult(Code.PARAM_REQUIRE);
        }
        if (BaseContext.getCurrentId()==null) {
            return Result.errorResult(Code.NEED_LOGIN);
        }
        Course checkCourse = courseMapper.selectById(dto.getCourseId());
        if (checkCourse==null) {
            return Result.errorResult(Code.DATA_NOT_EXIST);
        }
        int checkRemove = courseMapper.deleteById(dto.getCourseId());
        if (checkRemove==0) {
            return Result.errorResult(Code.SERVER_ERROR);
        }

        return Result.okResult(Code.SUCCESS);
    }

    @Override
    public Result updateGetCourse(AdminCourseUpdateGetDto dto) {

        if (dto==null) {
            return Result.errorResult(Code.PARAM_REQUIRE);
        }
        if (BaseContext.getCurrentId()==null) {
            return Result.errorResult(Code.NEED_LOGIN);
        }
        Course course = courseMapper.selectById(dto.getCourseId());
        if (course==null) {
            return Result.errorResult(Code.DATA_NOT_EXIST);
        }

        return Result.okResult(course);
    }

    @Override
    public Result updateCourse(AdminCourseUpdateDto dto) {

        if (dto==null) {
            return Result.errorResult(Code.PARAM_REQUIRE);
        }
        if (BaseContext.getCurrentId()==null) {
            return Result.errorResult(Code.NEED_LOGIN);
        }
        Course checkCourse = courseMapper.selectById(dto.getCourseId());
        if (checkCourse==null) {
            return Result.errorResult(Code.DATA_NOT_EXIST);
        }
        Course course=new Course();
        BeanUtils.copyProperties(checkCourse,course);
        if (dto.getCourseName()!=null) {
            course.setCourseName(dto.getCourseName());
        }
        if (dto.getCourseDay()!=null) {
            course.setCourseDay(dto.getCourseDay());
        }
        if (dto.getCourseWeekStart()!=null) {
            course.setCourseWeekStart(dto.getCourseWeekStart());
        }
        if (dto.getCourseWeekEnd()!=null) {
            course.setCourseWeekEnd(dto.getCourseWeekEnd());
        }
        if (dto.getCourseTimeStart()!=null) {
            course.setCourseTimeStart(dto.getCourseTimeStart());
        }
        if (dto.getCourseTimeEnd()!=null) {
            course.setCourseTimeEnd(dto.getCourseTimeEnd());
        }
        if (dto.getCourseAddress()!=null&&!dto.getCourseAddress().equals("")) {
            course.setCourseAddress(dto.getCourseAddress());
        }
        if (dto.getCourseTeacher()!=null&&!dto.getCourseTeacher().equals("")) {
            course.setCourseTeacher(dto.getCourseTeacher());
        }
        if (dto.getSemesterId()!=null) {
            course.setSemesterId(dto.getSemesterId());
        }
        if (dto.getGrade()!=null&&!dto.getGrade().equals("")&&dto.getGrade().length()!=0) {
            course.setGrade(dto.getGrade());
        }
        int checkUpdate = courseMapper.updateById(course);
        if (checkUpdate==0) {
            return Result.errorResult(Code.SERVER_ERROR);
        }

        return Result.okResult(Code.SUCCESS);
    }

    @Override
    public Result getAdminCourseList(AdminGetListDto dto) {
        if (BaseContext.getCurrentId()==null) {
            return Result.errorResult(Code.NEED_LOGIN);
        }
        dto.checkParam();
        IPage page=new Page(dto.getPage(),dto.getSize());
        LambdaQueryWrapper<Course> wrapper=new LambdaQueryWrapper<>();
        if (dto.getMimo()!=null&&!dto.getMimo().equals("")) {
            wrapper.like(Course::getCourseName,dto.getMimo());
            wrapper.like(Course::getCourseTeacher,dto.getMimo());
        }
        page=page(page,wrapper);
        Result result=new PageResponseResult(dto.getPage(),dto.getSize(), (int) page.getTotal());
        result.setData(page.getRecords());
        return Result.okResult(result);
    }

    @Async
    public String checkSemester(Long semesterId){

        Semester bigSemester = semesterMapper.getBigId();
        String courseSemesterId= String.valueOf(bigSemester.getSemesterId());

        if (semesterId!=null) {
            courseSemesterId= String.valueOf(semesterId);
        }
        return courseSemesterId;
    }

}




